package com.leyou.item.service.impl;

import com.baomidou.mybatisplus.core.toolkit.CollectionUtils;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.leyou.common.dto.PageDTO;
import com.leyou.common.exceptions.LyException;
import com.leyou.item.dto.SkuDTO;
import com.leyou.item.dto.SpuDTO;
import com.leyou.item.entity.*;
import com.leyou.item.mapper.SpuMapper;
import com.leyou.item.service.*;
import org.springframework.amqp.core.AmqpTemplate;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;

import static com.leyou.common.constants.MQConstants.ExchangeConstants.ITEM_EXCHANGE_NAME;
import static com.leyou.common.constants.MQConstants.RoutingKeyConstants.ITEM_DOWN_KEY;
import static com.leyou.common.constants.MQConstants.RoutingKeyConstants.ITEM_UP_KEY;

@Service
public class SpuServiceImpl extends ServiceImpl<SpuMapper, Spu> implements SpuService {
    @Autowired
    private SkuService skuService;
    @Autowired
    private SpuDetailService spuDetailService;
    @Autowired
    private BrandService brandService;
    @Autowired
    private CategoryService categoryService;
    @Autowired
    private AmqpTemplate amqpTemplate;

    //分页查询
    @Override
    public PageDTO<SpuDTO> quryPaGe(Integer page, Integer rows, Boolean saleable, Long categoryId, Long brandId, Long id) {

        // 健壮性判断
        int current = Math.max(page, 1);
        int size = Math.max(rows, 5);
        //查询条件拼装
        Page<Spu> list = query().eq(id != null, "id", id)
                .eq(saleable != null, "saleable", saleable)
                .eq(categoryId != null, "cid3", categoryId)
                .eq(brandId != null, "brand_id", brandId).page(new Page<>(current, size));
        //获取数据
        List<Spu> records = list.getRecords();
        //po转换为dto
        List<SpuDTO> dtoList = SpuDTO.convertEntityList(records);
        for (SpuDTO spuDTO : dtoList) {
            BrandCategoryBylist(spuDTO);
        }

        //返回结果
        return new PageDTO<>(list.getTotal(), list.getPages(), dtoList);
    }

    //添加商品
    @Override
    @Transactional
    public void add(SpuDTO spuDTO) {
        // 1.新增Spu
        Spu spu = spuDTO.toEntity(Spu.class);
        spu.setSaleable(false);
        boolean success = save(spu);
        if (!success) {
            throw new LyException(500, "新增商品失败");
        }
        // 2.新增SpuDetail
        SpuDetail spuDetail = spuDTO.getSpuDetail().toEntity(SpuDetail.class);
        spuDetail.setSpuId(spu.getId());
        success = spuDetailService.save(spuDetail);
        if (!success) {
            throw new LyException(500, "新增商品详情失败");
        }
        // 3.新增Sku
        List<Sku> list = spuDTO.getSkus().stream().map(skuDTO -> {
            Sku sku = skuDTO.toEntity(Sku.class);
            sku.setSaleable(false);
            sku.setSpuId(spu.getId());
            return sku;
        }).collect(Collectors.toList());
        // 批量新增
        skuService.saveBatch(list);

    }


    //修改商品
    @Override
    @Transactional
    public void updateSpu(SpuDTO spuDTO) {
        // 1.修改spu
        // 1.1.判断是否存在spu的id，有说明需要修改，没有说明不需要
        Long spuId = spuDTO.getId();
        boolean success = false;
        if (spuId != null) {
            Spu spu = spuDTO.toEntity(Spu.class);
            spu.setSaleable(null);
            success = updateById(spu);
            if (!success) {
                // 更新失败，抛出异常
                throw new LyException(500, "更新商品失败！");
            }
        }

        // 2.修改spuDetail
        if (spuDTO.getSpuDetail() != null && spuDTO.getSpuDetail().getSpuId() != null) {
            SpuDetail spuDetail = spuDTO.getSpuDetail().toEntity(SpuDetail.class);
            success = spuDetailService.updateById(spuDetail);
            if (!success) {
                // 更新失败，抛出异常
                throw new LyException(500, "更新商品详情失败！");
            }
        }

        // 3.修改sku
        List<SkuDTO> skuDTOList = spuDTO.getSkus();
        if (CollectionUtils.isEmpty(skuDTOList)) {
            return;
        }

        // 3.2.转换DTO，并将sku根据saleable是否为null来分组。null，是新增或修改，不是null是删除
        Map<Boolean, List<Sku>> map = skuDTOList.stream()
                .map(skuDTO -> skuDTO.toEntity(Sku.class))
                .collect(Collectors.groupingBy(sku -> sku.getSaleable() == null));

        List<Sku> delSkuList = map.get(false);
        if (!CollectionUtils.isEmpty(delSkuList)) {
            skuService.removeByIds(delSkuList.stream()
                    .map(Sku::getId)
                    .collect(Collectors.toList()));
        }

        // 3.3.获取要新增或修改的sku
        List<Sku> insertOrUpdateList = map.get(true);
        // 如果不为空，则修改或新增
        if (!CollectionUtils.isEmpty(insertOrUpdateList)) {
            skuService.saveOrUpdateBatch(insertOrUpdateList);
        }
    }




        //上架下架商品
    @Override
    @Transactional
    public void RackDownModify(Long id, Boolean saleable) {
        Spu spu = new Spu();
        spu.setId(id);
        spu.setSaleable(saleable);
        boolean b = updateById(spu);
        if (b==false){
            throw new LyException(500,"更新失败");
        }
        boolean update = skuService.update().eq("spu_id", id).set("saleable", saleable).update();
        if (update==false){
            throw new LyException(500,"更新失败");
        }
        //发送消息
        String routingkey=saleable?ITEM_UP_KEY:ITEM_DOWN_KEY;
        amqpTemplate.convertAndSend(ITEM_EXCHANGE_NAME,routingkey,id);
    }

    //根据id查询spu及sku、spuDetail
    @Override
    public SpuDTO queryGoodsById(Long id) {
        // 1.查询spu
        Spu spu = getById(id);
        if (spu == null) {
            throw new LyException(400, "商品id不存在！");
        }
        //转换DTO
        SpuDTO spuDTO = new SpuDTO(spu);
        //查询spuDetail
        spuDTO.setSpuDetail(spuDetailService.queryById(id));
        // 3.查询sku
        spuDTO.setSkus(skuService.queryById(id));

        //准备商品分类和品牌名称
        BrandCategoryBylist(spuDTO);

        return spuDTO;
    }
    private void BrandCategoryBylist(SpuDTO spuDTO) {
        // 根据品牌id查询品牌名称
        Brand brand = brandService.getById(spuDTO.getBrandId());
        if(brand != null) {
            spuDTO.setBrandName(brand.getName());
        }
        // 根据三级分类id查询分类集合
        List<Category> categories = categoryService.listByIds(spuDTO.getCategoryIds());
        if(!CollectionUtils.isEmpty(categories)) {
            // 取出分类的名称，拼接起来
            String names = categories.stream().map(Category::getName).collect(Collectors.joining("/"));
            spuDTO.setCategoryName(names);
        }

    }
}